package com.itic.appbase.framework.xcx.utils;

import java.awt.Menu;
import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.net.ConnectException;
import java.net.URL;
import java.net.URLEncoder;
import java.security.SecureRandom;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.SortedMap;
import java.util.TreeMap;

import javax.net.ssl.HttpsURLConnection;
import javax.net.ssl.SSLContext;
import javax.net.ssl.SSLSocketFactory;
import javax.net.ssl.TrustManager;

import org.apache.commons.httpclient.util.HttpURLConnection;
import org.apache.http.HttpEntity;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.conn.ssl.SSLConnectionSocketFactory;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.dom4j.Document;
import org.dom4j.DocumentException;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.itic.appbase.framework.utils.DateHelper;
import com.itic.appbase.framework.utils.NumberStringHelper;
import com.itic.appbase.framework.utils.wxpay.MD5Utils;
import com.itic.appbase.framework.utils.wxpay.ReadSSl;
import com.itic.appbase.framework.utils.wxpay.SignUtils;
import com.itic.appbase.framework.utils.wxpay.StringUtils;
import com.itic.appbase.framework.utils.wxrefound.WeixinRefoundConfig;
import com.itic.appbase.framework.xcx.vo.WXPayResult;
import com.itic.appbase.framework.xcx.vo.WXRefundResult;

import net.sf.json.JSONObject;


/**
 * 微信工具，http 请求
 * @author 王文鑫
 * @date 2017年6月13日
 */
public class WeixinUtil {
	//public  static final String notifyUrl = "http://develop.jhjvip.cn:8080/mall/xcx/wx/pay/success";
	
	//public  static final String notifyUrl = "https://www.huifakeji.com/edu/mobile/order/success";
	private static Logger log = LoggerFactory.getLogger(WeixinUtil.class);
	
	public static JSONObject httpRequest(String requestUrl, String requestMethod, String outputStr){  
	    JSONObject jsonObject = null;  
	    StringBuffer buffer = new StringBuffer();  
	    try  
	    {  
	      TrustManager[] tm = { new MyX509TrustManager() };  
	      SSLContext sslContext = SSLContext.getInstance("SSL", "SunJSSE");  
	      sslContext.init(null, tm, new SecureRandom());  
	  
	      SSLSocketFactory ssf = sslContext.getSocketFactory();  
	  
	      URL url = new URL(requestUrl);  
	      HttpsURLConnection httpUrlConn = (HttpsURLConnection)url.openConnection();  
	      httpUrlConn.setSSLSocketFactory(ssf);  
	  
	      httpUrlConn.setDoOutput(true);  
	      httpUrlConn.setDoInput(true);  
	      httpUrlConn.setUseCaches(false);  
	  
	      httpUrlConn.setRequestMethod(requestMethod);  
	  
	      if ("GET".equalsIgnoreCase(requestMethod)) {  
	        httpUrlConn.connect();  
	      }  
	  
	      if (outputStr != null) {  
	        OutputStream outputStream = httpUrlConn.getOutputStream();  
	  
	        outputStream.write(outputStr.getBytes("UTF-8"));  
	        outputStream.close();  
	      }  
	  
	      InputStream inputStream = httpUrlConn.getInputStream();  
	      InputStreamReader inputStreamReader = new InputStreamReader(inputStream, "utf-8");  
	      BufferedReader bufferedReader = new BufferedReader(inputStreamReader);  
	  
	      String str = null;  
	      while ((str = bufferedReader.readLine()) != null) {  
	        buffer.append(str);  
	      }  
	      bufferedReader.close();  
	      inputStreamReader.close();  
	  
	      inputStream.close();  
	      inputStream = null;  
	      httpUrlConn.disconnect();  
	      jsonObject = JSONObject.fromObject(buffer.toString());  
	    } catch (ConnectException ce) {  
	    	System.out.println("Weixin server connection timed out.");  
	    } catch (Exception e) {  
	    	System.out.println("https request error:{}"+ e);  
	    }  
	    return jsonObject;  
	  }
	
	  public static String urlEncode(String source, String encode) {
	        String result = source;  
	        try {  
	            result = URLEncoder.encode(source, encode);  
	        } catch (UnsupportedEncodingException e) {  
	            e.printStackTrace();  
	        }  
	        return result;  
	    } 
	// 获取access_token的接口地址（GET） 限200（次/天）  
		public final static String access_token_url = "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=APPID&secret=APPSECRET";  
		
		/** 
		 * 获取access_token 
		 *  
		 * @param appid 凭证 
		 * @param appsecret 密钥 
		 * @return 
		 *//*  
		public static  AccessToken getAccessToken(String appid, String appsecret) {  
		    AccessToken accessToken = null;  
		  
		    String requestUrl = access_token_url.replace("APPID", appid).replace("APPSECRET", appsecret);  
		    JSONObject jsonObject = httpRequest(requestUrl, "GET", null);  
		    // 如果请求成功  
		    if (null != jsonObject) {  
		        try {  
		            accessToken = new AccessToken();  
		            accessToken.setToken(jsonObject.getString("access_token"));  
		            accessToken.setExpiresIn(jsonObject.getInt("expires_in"));  
		        } catch (JSONException e) {  
		            accessToken = null;  
		            // 获取token失败  
		            log.error("获取token失败 errcode:{} errmsg:{}", jsonObject.getInt("errcode"), jsonObject.getString("errmsg"));  
		        }  
		    }  
		    return accessToken;  
		}  */

		// 菜单创建（POST） 限100（次/天）  
		public static String menu_create_url = "https://api.weixin.qq.com/cgi-bin/menu/create?access_token=ACCESS_TOKEN";  
		  
		/** 
		 * 创建菜单 
		 *  
		 * @param menu 菜单实例 
		 * @param accessToken 有效的access_token 
		 * @return 0表示成功，其他值表示失败 
		 */  
		public static int createMenu(Menu menu, String accessToken) {  
		    int result = 0;  
		  
		    // 拼装创建菜单的url  
		    String url = menu_create_url.replace("ACCESS_TOKEN", accessToken);  
		    // 将菜单对象转换成json字符串  
		    String jsonMenu = JSONObject.fromObject(menu).toString();  
		    // 调用接口创建菜单  
		    JSONObject jsonObject = httpRequest(url, "POST", jsonMenu);  
		  
		    if (null != jsonObject) {  
		        if (0 != jsonObject.getInt("errcode")) {  
		            result = jsonObject.getInt("errcode");  
		            log.error("创建菜单失败 errcode:{} errmsg:{}", jsonObject.getInt("errcode"), jsonObject.getString("errmsg"));  
		        }  
		    }  
		  
		    return result;  
		}
		
	
		public static WXPayResult  wxPay(String openId,String appId,String mchId,String mchKey,String orderNo,double actualPay,String spbillCreateIp,String body,String notifyUrl) {
			//支付密钥
			String key = "&key="+mchKey;
			//交易类型
			String tradeType = "JSAPI";
			//随机字符串
			String nonceStr = getNonceStr();
			//微信用户唯一id
			 Map<String, String> sParaTemp = new HashMap<String, String>();
			 sParaTemp.put("appid", appId);
			 //sParaTemp.put("attach", AppSecret);
			 sParaTemp.put("body",  body);
			 sParaTemp.put("mch_id", mchId);       
			 sParaTemp.put("nonce_str", nonceStr);
			 sParaTemp.put("notify_url",notifyUrl);
			 sParaTemp.put("openid", openId);
			 sParaTemp.put("out_trade_no", orderNo);
			 sParaTemp.put("spbill_create_ip", spbillCreateIp);
			 //实际支付金额,已分为单位
			 String totalFee = NumberStringHelper.mulString(Double.toString(actualPay), "100", 0);
			 sParaTemp.put("total_fee",totalFee);

			 sParaTemp.put("trade_type", tradeType);
			 //去掉空值 跟 签名参数(空值不参与签名，所以需要去掉)
			 Map<String, String> map = paraFilter(sParaTemp);
			/**
			按照 参数=参数值&参数2=参数值2 这样的形式拼接（拼接需要按照ASCII码升序排列）
			*/
			String mapStr = createLinkString(map);
			//MD5运算生成签名
			String sign =sign(mapStr, key, "utf-8").toUpperCase();
			sParaTemp.put("sign", sign);
			/** 
			组装成xml参数,此处偷懒使用手动组装，严格代码可封装一个方法，XML标排序需要注意，ASCII码升序排列 
			*/
			 String xml = "<xml>" + "<appid>" + appId + "</appid>" 
					 	//+ "<attach>" + AppSecret + "</attach>" 
	                   	+ "<body>" + body + "</body>" 
	                    + "<mch_id>" + mchId + "</mch_id>" 
	                    + "<nonce_str>" + nonceStr + "</nonce_str>" 
	                    + "<notify_url>" + notifyUrl + "</notify_url>" 
	                    + "<openid>" + openId + "</openid>" 
	                    + "<out_trade_no>" + orderNo + "</out_trade_no>" 
	                    + "<spbill_create_ip>" + spbillCreateIp + "</spbill_create_ip>" 
	                    + "<total_fee>"+totalFee+"</total_fee>"
	                    + "<trade_type>" + tradeType + "</trade_type>" 
	                    + "<sign>" + sign + "</sign>"
	                    + "</xml>";
	        //统一下单url，生成预付id
	        String url = "https://api.mch.weixin.qq.com/pay/unifiedorder";
	        //请求数据
	        String result = XCXHttpRequest(url, "POST", xml);
	        WXPayResult  wxPayResult = parseWXPayResult(result,appId,key);
	        return wxPayResult;

		}
		
		public static WXPayResult parseWXPayResult(String result,String appId,String key) {
			String timeStamp = String.valueOf(System.currentTimeMillis() / 1000);
	        //得到预支付id
	        WXPayResult wxPayResult = getPayNo(result);
	        if("SUCCESS".equals(wxPayResult.getError_code())) {
	        	String packages = "prepay_id="+wxPayResult.getPrepay_id();
	        	String nonceStr = getNonceStr();
	        	//开始第二次签名
	        	String mapStr1 = "appId="+appId+"&nonceStr=" + nonceStr + "&package=prepay_id=" + wxPayResult.getPrepay_id() + "&signType=MD5&timeStamp=" + timeStamp;
	        	String paySign = sign(mapStr1, key, "utf-8").toUpperCase();
	        	JSONObject obj = new JSONObject();
	        	obj.put("appId", appId);
	        	obj.put("timeStamp", timeStamp);
	        	obj.put("nonceStr", nonceStr);
	        	obj.put("package", packages);
	        	obj.put("signType", "MD5");
	        	obj.put("paySign", paySign);
	        	wxPayResult.setResult(obj);
	        }
			return wxPayResult;
		}


		public static String getNonceStr() {
		    //获得当前日期
		    Date now = new Date();
		    SimpleDateFormat outFormat = new SimpleDateFormat("yyyyMMddHHmmss");
		    String currTime = outFormat.format(now);
		    //截取8位
		    String strTime = currTime.substring(8, currTime.length());
		    //得到4位随机整数
		    int num = 1;
		    double random = Math.random();
		    if (random < 0.1) {
		        random = random + 0.1;
		    }
		    for (int i = 0; i < 4; i++) {
		        num = num * 10;
		    }
		    num = (int)random * num;
		    return strTime + num;
		}
		
		/**
	     * 除去数组中的空值和签名参数
	     * @param sArray 签名参数组
	     * @return 去掉空值与签名参数后的新签名参数组
	     */
	    public static Map<String, String> paraFilter(Map<String, String> sArray) {
	        Map<String, String> result = new HashMap<String, String>();
	        if (sArray == null || sArray.size() <= 0) {
	            return result;
	        }
	        for (String key : sArray.keySet()) {
	            String value = sArray.get(key);
	            if (value == null || value.equals("") || key.equalsIgnoreCase("sign")
	                    || key.equalsIgnoreCase("sign_type")) {
	                continue;
	            }
	            result.put(key, value);
	        }
	        return result;
	    }
	    
	    /**
	     * 把数组所有元素排序，并按照“参数=参数值”的模式用“&”字符拼接成字符串
	     * @param params 需要排序并参与字符拼接的参数组
	     * @return 拼接后字符串
	     */
	    public static String createLinkString(Map<String, String> params) {
	        List<String> keys = new ArrayList<String>(params.keySet());
	        Collections.sort(keys);

	        String prestr = "";

	        for (int i = 0; i < keys.size(); i++) {
	            String key = keys.get(i);
	            String value = params.get(key);
	            if (i == keys.size() - 1) {// 拼接时，不包括最后一个&字符
	                prestr = prestr + key + "=" + value;
	            } else {
	                prestr = prestr + key + "=" + value + "&";
	            }
	        }
	        return prestr;
	    }
	    
	    /**
	     * MD5 加密，转为指定类型
	     * @param text
	     * @param key
	     * @param input_charset
	     * @return
	     */
	    public static String sign(String text, String key, String input_charset) {
	        text = text + key;
	        String sign = MD5Utils.MD5Encode(text, input_charset).toUpperCase();
	        return sign;
	    }

	    public static byte[] getContentBytes(String content, String charset) {
	        if (charset == null || "".equals(charset)) {
	            return content.getBytes();
	        }
	        try {
	            return content.getBytes(charset);
	        } catch (UnsupportedEncodingException e) {
	            throw new RuntimeException("MD5签名过程中出现错误,指定的编码集不对,您目前指定的编码集是:" + charset);
	        }
	    }
	    
	    /**
	     * 
	     * @param requestUrl请求地址
	     * @param requestMethod请求方法
	     * @param outputStr参数
	     */
	    public static String httpRequest1(String requestUrl,String requestMethod,String outputStr){
	        // 创建SSLContext
	        StringBuffer buffer=null;
	        try{
	        URL url = new URL(requestUrl);
	        HttpURLConnection conn = (HttpURLConnection) url.openConnection();
	        conn.setRequestMethod(requestMethod);
	        conn.setDoOutput(true);
	        conn.setDoInput(true);
	        conn.connect();

	        //往服务器端写内容
	        if(null !=outputStr){
	            OutputStream os=conn.getOutputStream();
	            os.write(outputStr.getBytes("utf-8"));
	            os.close();
	        }
	        // 读取服务器端返回的内容
	        InputStream is = conn.getInputStream();
	        InputStreamReader isr = new InputStreamReader(is, "utf-8");
	        BufferedReader br = new BufferedReader(isr);
	        buffer = new StringBuffer();
	        String line = null;
	        while ((line = br.readLine()) != null) {
	                      buffer.append(line);
	        }
	        }catch(Exception e){
	            e.printStackTrace();
	        }
	        return buffer.toString();
	  }  
	    /**
	     * 解析微信放回的xml 为map
	     * @param result
	     * @return
	     */
	    public static Map<String, String> parseWXResult(String result){
	    	Map<String, String> map = new HashMap<String, String>();
	        InputStream in = new ByteArrayInputStream(result.getBytes());
	        SAXReader read = new SAXReader();
	        Document doc =null;
			try {
				doc = read.read(in);
			} catch (DocumentException e) {
				e.printStackTrace();
			}
	        //得到xml根元素
	        Element root = doc.getRootElement();
	        //遍历  得到根元素的所有子节点 
	        @SuppressWarnings("unchecked")
	        List<Element> list =root.elements();
	        for(Element element:list){
	            //装进map
	            map.put(element.getName(), element.getText());
	        }
	    	return map;
	    }
	    /**
	     * 解析微信退款返回结果
	     * @param result
	     * @return
	     */
	    public static WXRefundResult getWXRefundResult(String result) {
	    	Map<String, String> map = parseWXResult(result);
	    	 //返回码
	        String return_code = map.get("return_code");
	        //返回信息
	        String result_code = map.get("result_code");
	        //预支付id
	        String prepay_id = "";
	        //return_code 和result_code 都为SUCCESS 的时候返回 预支付id
	        WXRefundResult wxRefundResult = new WXRefundResult();
	        if(return_code.equals("SUCCESS")&&result_code.equals("SUCCESS")){
	        	String transaction_id = map.get("transaction_id");
	        	String nonce_str = map.get("nonce_str");
	        	String out_refund_no = map.get("out_refund_no");
	        	String sign = map.get("sign");
	        	String return_msg = map.get("return_msg");
	        	String mch_id = map.get("mch_id");
	        	String refund_id = map.get("refund_id");
	        	String out_trade_no = map.get("out_trade_no");
	        	String appid = map.get("appid");
	        	String refund_fee = map.get("refund_fee");
	        	String total_fee = map.get("total_fee");
	        	wxRefundResult.setError_code("SUCCESS");
	        	wxRefundResult.setError_reson(return_msg);
	        	wxRefundResult.setAppId(appid);
	        	wxRefundResult.setMchId(mch_id);
	        	wxRefundResult.setOutRefundNo(out_refund_no);
	        	wxRefundResult.setOutTradeNo(out_trade_no);
	        	wxRefundResult.setRefundFee(refund_fee);
	        	wxRefundResult.setTotalRefundFee(total_fee);
	        	wxRefundResult.setTransactionId(transaction_id);
	        	
	        }else {
	        	wxRefundResult.setError_code("FAIL");
	        	String err_code_des =map.get("err_code_des"); 
	        	String mch_id = map.get("mch_id");
	        	String appid = map.get("appid");
	        	wxRefundResult.setError_reson(err_code_des);
	        	wxRefundResult.setAppId(appid);
	        	wxRefundResult.setMchId(mch_id);
	        	wxRefundResult.setAppId(appid);
	        	wxRefundResult.setMchId(mch_id);
	        }
	    	return wxRefundResult;
	    	
	    	
	    }
	    
	    
	    /**
	     * 解析xml得到 prepay_id 预支付id
	     * @param result
	     * @return
	     * @throws DocumentException 
	     */
	    public static WXPayResult getPayNo(String result){
	        Map<String, String> map = parseWXResult(result);
	        //返回码
	        String return_code = map.get("return_code");
	        //返回信息
	        String result_code = map.get("result_code");
	        //预支付id
	        String prepay_id = "";
	        //return_code 和result_code 都为SUCCESS 的时候返回 预支付id
	        WXPayResult wxPayResult = new WXPayResult();
	        if(return_code.equals("SUCCESS")&&result_code.equals("SUCCESS")){
	            prepay_id = map.get("prepay_id");
	            wxPayResult.setError_code("SUCCESS");
	            wxPayResult.setPrepay_id(prepay_id);
	            
	        }else {
	        	 wxPayResult.setError_code("FAIL");
	        	 wxPayResult.setError_reson(result_code);
	        }
	        return wxPayResult;
	    }
	    
	    /**
	     * 小程序调用支付接口返回字符串数据
	     * @param requestUrl
	     * @param requestMethod
	     * @param outputStr
	     * @return
	     */
	    public static String XCXHttpRequest(String requestUrl, String requestMethod, String outputStr){  
		    JSONObject jsonObject = null;  
		    StringBuffer buffer = new StringBuffer();  
		    OutputStream outputStream =null;
		    InputStream inputStream =null;
		    InputStreamReader inputStreamReader = null;
		    BufferedReader bufferedReader = null;
		    HttpsURLConnection httpUrlConn = null;
		    try  
		    {  
		      TrustManager[] tm = { new MyX509TrustManager() };  
		      SSLContext sslContext = SSLContext.getInstance("SSL", "SunJSSE");  
		      sslContext.init(null, tm, new SecureRandom());  
		      SSLSocketFactory ssf = sslContext.getSocketFactory();  
		      URL url = new URL(requestUrl);  
		      httpUrlConn = (HttpsURLConnection)url.openConnection();  
		      httpUrlConn.setSSLSocketFactory(ssf);  
		      httpUrlConn.setDoOutput(true);  
		      httpUrlConn.setDoInput(true);  
		      httpUrlConn.setUseCaches(false);  
		      httpUrlConn.setRequestMethod(requestMethod);  
		      if ("GET".equalsIgnoreCase(requestMethod)) {  
		        httpUrlConn.connect();  
		      }  
		      if (outputStr != null) {  
		        outputStream = httpUrlConn.getOutputStream();  
		        outputStream.write(outputStr.getBytes("UTF-8"));  
		      }  
		  
		      inputStream = httpUrlConn.getInputStream();  
		      inputStreamReader = new InputStreamReader(inputStream, "utf-8");  
		      bufferedReader = new BufferedReader(inputStreamReader);  
		  
		      String str = null;  
		      while ((str = bufferedReader.readLine()) != null) {  
		        buffer.append(str);  
		      }
		    } catch (Exception e) {  
		    	e.printStackTrace();
		    }finally {
		    	try {
					outputStream.close();
					bufferedReader.close();  
				    inputStreamReader.close();  
				    inputStream.close(); 
				    httpUrlConn.disconnect(); 
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
		    return buffer.toString();  
		  }
	    
	    /**
	     * 解析 回调时的xml装进map 返回
	     * @param result 
	     * @return
	     * @throws DocumentException 
	     */
	    public static Map<String, String> getNotifyUrl(String result) throws DocumentException{
	        Map<String, String> map = new HashMap<String, String>();
	        InputStream in = new ByteArrayInputStream(result.getBytes());
	        SAXReader read = new SAXReader();
	        Document doc = read.read(in);
	        //得到xml根元素
	        org.dom4j.Element root = doc.getRootElement();
	        //遍历  得到根元素的所有子节点 
	        @SuppressWarnings("unchecked")
	        List<Element> list =root.elements();
	        for(Element element:list){
	            //装进map
	            map.put(element.getName().toString(), element.getText().toString());
	        }
	        return map;
	    }
	    
	    /**
	     * 验证签名，判断是否是从微信发过来
	     * 验证方法：接收微信服务器回调我们url的时候传递的xml中的参数 然后再次加密，看是否与传递过来的sign签名相同
	     * @param map
	     * @return
	     */
	    public static boolean verifyWeixinNotify(Map<String, String> map,String key) {  
	        //根据微信服务端传来的各项参数 进行再一次加密后  与传过来的 sign 签名对比
	        String mapStr = createLinkString(map);
	        String signOwn = sign(mapStr, key, "utf-8").toUpperCase();         //根据微信端参数进行加密的签名
	        String signWx = map.get("sign");                //微信端传过来的签名
	        if(signOwn.equals(signWx)){
	            //如果两个签名一致，验证成功
	            return true;
	        }
	        return false;
	    }  
	    
	    
	    /**
		 * 微信退款方法
		 * @param orderNum
		 * @param refundFee
		 * @param totalRefundFee
		 * @return
		 * @throws Exception
		 */
		public static String wxRefund(String appId,String mchId,String key,String caLicense,String outRefundNo,String orderNum,String refundFee,String totalRefundFee) throws Exception {
			 WeixinRefoundConfig config = new WeixinRefoundConfig();
			 String nonce_str1 =  StringUtils.getStrRandom(28);
			 //获取签名  enc_bank_no
			 //appId = "wx910d63f3cec2d59b";
			 //mchId = "1501717851";
			// key = "9ebcda3b0d16443c9c9734ea3e1e02f5";
			// caLicense = "D://apiclient_cert.p12";
		     SortedMap<Object,Object> parameters1 = new TreeMap<Object,Object>();
		     parameters1.put("appid", appId);
			 parameters1.put("mch_id", mchId);
			 parameters1.put("nonce_str", nonce_str1);
			 parameters1.put("out_trade_no", orderNum);
			// outRefundNo = IdGen.uuid();
			 parameters1.put("out_refund_no", outRefundNo);
			 refundFee ="0.01";
			 totalRefundFee="0.01";
			 refundFee = NumberStringHelper.mulString(refundFee, "100", 0);
			 totalRefundFee = NumberStringHelper.mulString(totalRefundFee, "100", 0);
			 parameters1.put("refund_fee", refundFee);
			 parameters1.put("total_fee", totalRefundFee);
			 //parameters1.put("notify_url", config.getNotify_url());
			 String sign1 = SignUtils.creatSign("UTF-8", key,parameters1);
			 //请求企业付款
			 TreeMap<String, String> tmap1 = new TreeMap<String, String>();
			 tmap1.put("appid", appId);
			 tmap1.put("mch_id",mchId);
			 tmap1.put("nonce_str", nonce_str1);
			 tmap1.put("out_trade_no", orderNum);
			 tmap1.put("out_refund_no", outRefundNo);
			 tmap1.put("refund_fee", refundFee);
			 tmap1.put("total_fee",totalRefundFee);
			 tmap1.put("sign", sign1);
			// tmap1.put("notify_url", config.getNotify_url());
			 String xml2 = getFilterRequestXml(tmap1);
			 String  xml3= httpClientResultRefound(xml2,"UTF-8",mchId,caLicense);
			 return xml3;
		}
		/**
		 * 将map转换成xml
		 * @param parameters
		 * @return
		 * @throws Exception
		 */
		@SuppressWarnings("rawtypes")
		public static String getFilterRequestXml(TreeMap<String, String> parameters)
				throws Exception {
			StringBuffer sb = new StringBuffer();
			sb.append("<xml>");
			Set es = parameters.entrySet();
			Iterator it = es.iterator();
			while (it.hasNext()) {
				Map.Entry entry = (Map.Entry) it.next();
				String k = (String) entry.getKey();
				String v = (String) entry.getValue();
				sb.append("<" + k + ">" + v + "</" + k + ">");
			}
			sb.append("</xml>");
			return sb.toString();
		}
	    
		/**
		 * httpClient 请求微信退款
		 * @param parms
		 * @return  
		 * @throws Exception
		 */
		public static String httpClientResultRefound(String xml,String charset,String mch_id, String pkcdPath12) throws Exception{
			StringBuffer reultBuffer = new StringBuffer();
			
			SSLConnectionSocketFactory sslsf = ReadSSl.getInstance().readCustomSSL(mch_id,pkcdPath12);

			HttpPost httpPost = new HttpPost("https://api.mch.weixin.qq.com/secapi/pay/refund");
	        CloseableHttpClient httpclient = HttpClients.custom().setSSLSocketFactory(sslsf).build();
	        StringEntity myEntity = new org.apache.http.entity.StringEntity(xml, charset);
	        myEntity.setContentType("text/xml;charset=UTF-8");
	        myEntity.setContentEncoding(charset);
	        httpPost.setHeader("Content-Type", "text/xml; charset=UTF-8");
	        httpPost.setEntity(myEntity);
	        
	        CloseableHttpResponse response      = null;
	        InputStream inputStream		        = null;
	        InputStreamReader inputStreamReader = null;
	        BufferedReader bufferedReader       = null;
	        try {
	        	response = httpclient.execute(httpPost);
	        	HttpEntity entity = response.getEntity();
				if (entity!=null){
					inputStream = entity.getContent();
					inputStreamReader = new InputStreamReader(inputStream, charset);
					bufferedReader = new BufferedReader(inputStreamReader);
					String str = null;
					while ((str = bufferedReader.readLine()) != null) {
						reultBuffer.append(str);
					}
				}
			} catch (ClientProtocolException e) {
				e.printStackTrace();
			} catch (IOException e) {
				e.printStackTrace();
			}finally{

				httpclient.close();
				response.close();
				bufferedReader.close();
				inputStreamReader.close();
				inputStream.close();
				inputStream = null;
			}
	    
	        return reultBuffer.toString();
		}
	    public static void main(String[] args) throws Exception {
	    	/*String openId = "ori3i5M44LzIUw9z5bSzhU07xSrI";
	    	String appId = "wx910d63f3cec2d59b";
	    	String mchId ="1501717851";
	    	String AppSecret ="9ebcda3b0d16443c9c9734ea3e1e02f5";
	    	//wxPay(openId, appId, mchId, AppSecret, "201805081658", 100, "192.168.1.107", "abcd","www.uhuijia.com.cn");
	    	wxRefund("", "", "", "", "", "201805181033685200", "0.01", "0.01");*/
	    	
	    	String timeStr = "2018-05-12 23:04:19";
	    	Date date = DateHelper.parseDate(timeStr);
	    	long d = date.getTime();
	    	System.out.println(d);
	    			
	    }

}
